package cn.itcast.controller;

import cn.hutool.core.collection.CollUtil;
import cn.hutool.core.util.ObjectUtil;
import cn.itcast.constant.MessageConstant;
import cn.itcast.entity.PageResult;
import cn.itcast.entity.Result;
import cn.itcast.pojo.User;
import cn.itcast.pojo.UserInfo;
import cn.itcast.service.UserService;
import com.alibaba.dubbo.config.annotation.Reference;
import lombok.extern.slf4j.Slf4j;
import org.springframework.http.HttpStatus;
import org.springframework.http.ResponseEntity;
import org.springframework.security.access.prepost.PreAuthorize;
import org.springframework.security.core.Authentication;
import org.springframework.security.core.context.SecurityContextHolder;
import org.springframework.web.bind.annotation.*;

import java.util.List;

@RestController
@RequestMapping("/user")
@Slf4j
public class UserController {
    @Reference
    private UserService userService;

    @GetMapping("/getUsername")
    public ResponseEntity<Result> getUsername() {
        Result result = new Result();
        try {
            UserInfo userInfo = (UserInfo) SecurityContextHolder.getContext().getAuthentication().getPrincipal();
            if (ObjectUtil.isNotEmpty(userInfo)) {
                result.setFlag(true);
                result.setMessage(MessageConstant.QUERY_USER_SUCCESS);
                result.setData(userInfo.getUsername());
                return ResponseEntity.ok(result);
            }

        } catch (Exception e) {
            log.error(MessageConstant.QUERY_USER_FAIL, e);
        }
        result.setFlag(false);
        result.setMessage(MessageConstant.QUERY_USER_FAIL);
        return ResponseEntity.ok(result);
    }

    @PreAuthorize("hasAuthority('USER_EDIT')")
    @PutMapping
    public ResponseEntity<Result> edit(@RequestParam("roleIds") List<Integer> roleIds,
                                       @RequestBody User user) {
        Result result = new Result();
        try {
            UserInfo userInfo = (UserInfo) SecurityContextHolder.getContext().getAuthentication().getPrincipal();
            Boolean flag = userService.edit(roleIds, user);
            if (flag) {
                result.setFlag(true);
                result.setMessage(MessageConstant.EDIT_USER_SUCCESS);
                return ResponseEntity.ok(result);
            }
        } catch (Exception e) {
            log.error(MessageConstant.EDIT_USER_FAIL, e);
        }
        result.setFlag(false);
        result.setMessage(MessageConstant.EDIT_USER_FAIL);
        return ResponseEntity.ok(result);
    }

    @PreAuthorize("hasAuthority('USER_DELETE')")
    @DeleteMapping("/{id}")
    public ResponseEntity<Result> delete(@PathVariable Integer id) {
        Result result = new Result();
        try {
            Boolean flag = userService.delete(id);
            if (flag) {
                result.setFlag(true);
                result.setMessage(MessageConstant.DELETE_USER_SUCCESS);
                return ResponseEntity.ok(result);
            }
        } catch (Exception e) {
            log.error(MessageConstant.DELETE_USER_FAIL, e);
        }
        result.setFlag(false);
        result.setMessage(MessageConstant.DELETE_USER_FAIL);
        return ResponseEntity.ok(result);
    }


    /**
     * 新建
     *
     * @return
     */
    @PostMapping
    @PreAuthorize("hasAuthority('USER_ADD')")
    public ResponseEntity<Result> saveUser(@RequestParam("roleIds") List<Integer> roleIds,
                                           @RequestBody User user) {
        Result result = new Result();
        try {
            Boolean flag = userService.save(roleIds, user);
            if (flag) {
                result.setFlag(true);
                result.setMessage(MessageConstant.ADD_USER_SUCCESS);
                return ResponseEntity.ok(result);
            }
        } catch (Exception e) {
            log.error(MessageConstant.ADD_USER_FAIL, e);
        }
        result.setFlag(false);
        result.setMessage(MessageConstant.ADD_USER_FAIL);
        return ResponseEntity.ok(result);
    }

    @GetMapping("/all")
    public ResponseEntity<Result> findAll() {
        Result result = new Result();
        try {
            List<User> userList = userService.findAll();
            if (ObjectUtil.isNotEmpty(userList)) {
                result.setFlag(true);
                result.setMessage(MessageConstant.QUERY_USER_SUCCESS);
                result.setData(userList);
                return ResponseEntity.ok(result);
            }

        } catch (Exception e) {
            log.error(MessageConstant.QUERY_USER_FAIL, e);
        }
        result.setFlag(false);
        result.setMessage(MessageConstant.QUERY_USER_FAIL);
        return ResponseEntity.ok(result);
    }

    /**
     * 查询
     *
     * @param currentPage
     * @param pageSize
     * @param queryString
     * @return
     */
    @PreAuthorize("hasAuthority('USER_QUERY')")
    @GetMapping("/page")
    public ResponseEntity<Result> findByPage(@RequestParam(value = "currentPage", defaultValue = "1") Integer currentPage,
                                             @RequestParam(value = "pageSize", defaultValue = "10") Integer pageSize,
                                             @RequestParam(value = "queryString", required = false) String queryString) {
        Result result = new Result();
        try {
            PageResult pageResult = userService.findByPage(currentPage, pageSize, queryString);
            if (ObjectUtil.isNotEmpty(pageResult)) {
                result.setFlag(true);
                result.setMessage(MessageConstant.QUERY_USER_SUCCESS);
                result.setData(pageResult);
                return ResponseEntity.ok(result);
            }

        } catch (Exception e) {
            log.error(MessageConstant.QUERY_USER_FAIL, e);
        }
        result.setFlag(false);
        result.setMessage(MessageConstant.QUERY_USER_FAIL);
        return ResponseEntity.ok(result);
    }

    @GetMapping("/{id}")
    public ResponseEntity<Result> findById(@PathVariable Integer id) {
        Result result = new Result();
        try {
            User user = userService.findById(id);
            if (ObjectUtil.isNotEmpty(user)) {
                result.setFlag(true);
                result.setMessage(MessageConstant.QUERY_USER_SUCCESS);
                result.setData(user);
                return ResponseEntity.ok(result);
            }

        } catch (Exception e) {
            log.error(MessageConstant.QUERY_USER_FAIL, e);
        }
        result.setFlag(false);
        result.setMessage(MessageConstant.QUERY_USER_FAIL);
        return ResponseEntity.ok(result);
    }

    @GetMapping("/{id}/roleIds")
    public ResponseEntity<Result> findRoleIdsByUserId(@PathVariable Integer id) {
        Result result = new Result();
        try {
            List<Integer> roleIds = userService.findRoleIdsByUserId(id);
            if (CollUtil.isNotEmpty(roleIds)) {
                result.setFlag(true);
                result.setMessage(MessageConstant.QUERY_USER_SUCCESS);
                result.setData(roleIds);
                return ResponseEntity.ok(result);
            }

        } catch (Exception e) {
            log.error(MessageConstant.QUERY_USER_FAIL, e);
        }
        result.setFlag(false);
        result.setMessage(MessageConstant.QUERY_USER_FAIL);
        return ResponseEntity.ok(result);
    }
}
